package com.weseal.handler;

import com.weseal.enums.BaseEnum;
import org.apache.ibatis.type.BaseTypeHandler;
import org.apache.ibatis.type.JdbcType;
import org.springframework.util.StringUtils;

import java.sql.CallableStatement;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;

/**
 * @author weseal
 * @title
 * @description
 * @usage
 * @copyright Copyright 2014  rrmj Corporation. All rights reserved.
 * @company 上海众多美网络科技有限公司
 * @create 2017/9/10
 */
public final class UniversalEnumHandler<E extends BaseEnum> extends BaseTypeHandler<E> {

	private Class<E> type;
	private E[] enums;

	public UniversalEnumHandler(Class<E> type) {
		if (type == null) {
			throw new IllegalArgumentException("不能为空");
		}
		this.type = type;
		this.enums = type.getEnumConstants();
		if (this.enums == null)
			throw new IllegalArgumentException(type.getSimpleName()
					+ " does not represent an enum type.");
	}


	@Override
	public void setNonNullParameter(PreparedStatement preparedStatement, int i, E param, JdbcType jdbcType) throws SQLException {
		preparedStatement.setObject(i, (Integer) param.getCode(), jdbcType.TYPE_CODE);
	}

	@Override
	public E getNullableResult(ResultSet resultSet, String s) throws SQLException {
		int enumValue = resultSet.getInt(s);
		if (StringUtils.isEmpty(enumValue)) {
			return null;
		}
		return findEnum(enumValue);

	}

	@Override
	public E getNullableResult(ResultSet resultSet, int i) throws SQLException {
		int enumValue = resultSet.getInt(i);
		if (StringUtils.isEmpty(enumValue)) {
			return null;
		}
		return findEnum(enumValue);
	}

	@Override
	public E getNullableResult(CallableStatement callableStatement, int i) throws SQLException {
		int enumValue = callableStatement.getInt(i);
		if (StringUtils.isEmpty(enumValue)) {
			return null;
		}
		return findEnum(enumValue);
	}


	private E findEnum(Integer value) {
		if (value != null) {
			for (E e : enums) {
				if (e.getCode().equals(value)) {
					return e;
				}
			}
		}
		return null;
	}
}
